package com.opennews.openplatform

import grails.compiler.GrailsCompileStatic
import grails.gorm.transactions.Transactional
import groovy.transform.CompileDynamic
import org.hibernate.criterion.CriteriaSpecification
import org.springframework.beans.factory.annotation.Value

@Transactional(readOnly = true)
@GrailsCompileStatic
class RegionService {
    @Value('${openplatform.resource.httpBaseUrl}')
    String httpBaseUrl

    @Value('${openplatform.resource.regionFlagUrl}')
    String regionFlagUrl

    /**
     * Prepares the initial data for region.
     */
    @Transactional
    void init() {
        if (Region.count() == 0) {
            new Region(title: "柬埔寨", name: "cambodia").save()
            new Region(title: "马来西亚", name: "malaysian").save()
            new Region(title: "新加坡", name: "singapore").save()
            new Region(title: "泰国", name: "thailand").save()
        }
    }

    /**
     * Gets region flag url based on its name.
     * @param name: The region name.
     * @return The full url of the region flag.
     */
    String getFlagUrl(String name) {
        return !SharedUtil.isNullOrEmpty(name) ? "$httpBaseUrl$regionFlagUrl/${name.toLowerCase()}.png" : ""
    }

    /**
     * Queries all regions.
     * @return List of map instance which contains keys below.
     *          id: String of region id.
     *          name: String of region name.
     *          title: String of region title.
     *          flagUrl: String of region flag url.
     */
    @CompileDynamic
    List<Map<String, ?>> queryAll() {
        return Region.createCriteria().list {
            // Transforms the result data format to Map instance.
            resultTransformer(CriteriaSpecification.ALIAS_TO_ENTITY_MAP)

            // Specifies the property we need.
            projections {
                property("id", "id")
                property("name", "name")
                property("title", "title")
            }

            // Sets the orderby.
            order("name", "asc")
        }.each { Map<String, ?> item ->
            // Adds logoUrl key to this map item.
            item.flagUrl = getFlagUrl(item.name.toString())
        } as List<Map<String, ?>>
    }
}
